<template>
    <div class="vir-calendar">
        <div class="calendar-tool">
            <div class="calendar-tool-btn" @click="doClickMonth(-1)">上月</div>
            <div class="calendar-tool-info">{{title}}</div>
            <div class="calendar-tool-btn" @click="doClickMonth(1)">下月</div>
        </div>
        <div class="calendar-table">
            <div class="calendar-table-row calendar-table-week">
                <div v-for="(item, index) in week" :key="index">{{item}}</div>
            </div>
            <div class="calendar-table-row calendar-table-day" v-for="(w1, idx1) in weeks" :key="idx1" v-if="table.length >= w1">
                <div v-for="(w2, idx2) in week" :key="idx2" :class="{'active':formatClass(w1, idx2)}" @click="doClickDay(w1, idx2)">{{formatDate(w1, idx2)}}</div>
            </div>
        </div>
    </div>
</template>
<script lang="ts">
import { Component, Vue, Prop, Watch } from "vue-property-decorator";

@Component
export default class VirCalendar extends Vue {
    private day: number = 24 * 60 * 60 * 1000;
    private weeks: number[] = [7, 14, 21, 28, 35, 42];
    private week: string[] = ["日", "一", "二", "三", "四", "五", "六"];

    private table: Date[] = []; // 月历表
    private time: Date = new Date(); // 当前选中

    get title(): string {
        const y = this.time.getFullYear();
        const m = this.time.getMonth() + 1;

        return y + '-' + m;
    }

    /** 点击 菜单工具事件 */
    private doClickMonth(num: number) {
        const time = this.time;
        const m1 = time.getMonth();

        // 切换月份
        time.setMonth(m1 + num);

        this.onLoad(time);  // 刷新表格
        this.onClick(time); // 触发点击事件
    }

    /** 点击 表格事件 */
    private doClickDay(offset: number, idx: number) {
        const time = this.get(offset, idx);
        if (time == null) return;

        const m1 = time.getMonth();
        const m2 = this.time.getMonth();

        if (m1 !== m2) {
            this.onLoad(time);  // 刷新表格
            this.onClick(time); // 触发点击事件
        } else {
            this.time = time;
            this.onClick(time); // 触发点击事件
        }
    }

    /** 触发点击事件 */
    private onClick(time: Date) {
        this.$emit('calender-click', time);
    }

    private onLoad(date: Date) {
        const t = date.getTime();
        const day = this.day;

        // 获取月历表第一天
        date.setDate(1);
        const t1 = date.getDay();
        const t2 = date.getTime();
        const t3 = t2 - (t1 * day);

        // 遍历构建月历变
        const temp: Date[] = [];
        for (let i = 0; i < 42; i++) {
            temp.push(new Date(t3 + i * day));
        }

        // 赋值 & 刷新页面
        this.table = temp;
        this.time = new Date(t);
    }

    /** 格式化 - idx 验证是否选中 */
    private formatClass(offset: number, idx: number): boolean {
        if (!this.time) return false;

        const time = this.get(offset, idx);
        if (!time) return false;

        const d1: number = time.getTime();
        const d2: number = this.time.getTime();

        const t1 = d1 / this.day;
        const t2 = d2 / this.day;

        return t1 === t2;

    }

    /** 格式化 - idx 获取日期数 */
    private formatDate(offset: number, idx: number): string {
        const time = this.get(offset, idx);
        if (!time) return '?';

        return time.getDate() + '';
    }

    /** 获取 指定日期 */
    private get(offset: number, idx: number): Date | null {
        const index = offset + idx - 7;

        if (0 <= index && index < this.table.length) {
            return this.table[index];
        } else {
            return null;
        }
    }

    private mounted() {
        this.onLoad(new Date());
    }
}
</script>
<style lang="scss" scoped>
.vir-calendar {
  width: 100%;
  height: 100%;
  display: flex;
  overflow: hidden;
  flex-direction: column;
  border: 1px solid #eee;

  /* 月历工具 */
  .calendar-tool {
    height: 45px;
    display: flex;
    flex-direction: row;

    & > div {
      display: flex;
      align-items: center;
      justify-content: center;
    }

    .calendar-tool-btn {
      padding: 0 15px;
      cursor: pointer;
      color: #f8f8f8;
      background: #09283c;

      &:hover {
        background: #0d3854;
      }
    }

    .calendar-tool-info {
      flex: 1;
    }
  }

  /* 月历表 */
  .calendar-table {
    flex: 1;
    display: flex;
    flex-direction: column;

    .calendar-table-row {
      flex: 1;
      display: flex;
      flex-direction: row;

      & > div {
        flex: 1;
        display: flex;
        align-items: center;
        justify-content: center;
        border: 1px solid #eee;
        box-sizing: border-box;
      }
    }

    .calendar-table-week {
      background: #f8f8f8;
    }

    .calendar-table-day {
      & > div {
        cursor: pointer;

        &:hover {
          background: #7eeae4;
        }

        &.active {
          background: #46b5ae;
          color: #fff;
        }
      }
    }
  }
}
</style>
